﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Security.Principal;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Forms;
using System.Windows.Input;
using System.Windows.Media.Animation;
using System.Windows.Media.Imaging;
using UploadClient.Interfaces.Plugins;
using UploadClient.Interfaces.Upload;
using UploadClient.Utilitys;
using Application = System.Windows.Application;
using Clipboard = System.Windows.Clipboard;
using ComboBox = System.Windows.Controls.ComboBox;
using DataFormats = System.Windows.DataFormats;
using MessageBox = System.Windows.MessageBox;
using MouseEventArgs = System.Windows.Forms.MouseEventArgs;
using OpenFileDialog = Microsoft.Win32.OpenFileDialog;

namespace UploadClient
{
    public partial class oldMainWindow : Window, IHost
    {
        #region Parameter

        readonly List<UploadItem> filepath = new List<UploadItem>();
        readonly Options options = new Options(true);
        readonly ConnectionSettings settings = new ConnectionSettings(true);

        //FtpUpload ftpUpload = new FtpUpload();

        //Plugins
        // Plugins.ClipboardMonitoring.ClipboardMonitoring clipboardMonitoring = new Plugins.ClipboardMonitoring.ClipboardMonitoring();
        //Plugins.RegionShot.RegionShot regionShot = new Plugins.RegionShot.RegionShot();

        //Trayicon
        readonly NotifyIcon trayIcon = new NotifyIcon();
        readonly ContextMenuStrip trayMenu = new ContextMenuStrip();
        readonly ToolStripMenuItem trayMenuExit = new ToolStripMenuItem();
        bool commandLineException = false;
        oldSettingsWindow settingsWindow;

        #endregion

        #region Init

        public oldMainWindow()
        {
            InitializeComponent();

            //sets app titel
            string programName = GetProgramName();
            string version = GetProgramVersion();

            InitTrayIcon(programName);

            this.Loaded += new RoutedEventHandler(MainWindow_Loaded);


            //Init backgroundworker
            //ftpUpload.Init();
            //ftpUpload.UploadComplete += new UploadCompleteEventHandler(Upload_RunWorkerCompleted);
            //ftpUpload.UploadProgress += new UploadProgressEventHandler(Upload_ProgressChanged);

            //set handler for commandlineparam
            App.CommandLineArgs += new CommandLineArgsHandler(CommandLineArgs);

            // enables contextmenu only if user has adminrights
            if (new WindowsPrincipal(WindowsIdentity.GetCurrent()).IsInRole(WindowsBuiltInRole.Administrator))
                RegistryCheckBox.IsEnabled = true;

            //Init Plugins
            //clipboardMonitoring.Init(this);
            //regionShot.Init(this);

            //sets the values in the optionsmenu
            MonitoringClipboard.IsChecked = options.IsMonitoringClipboardCheckboxChecked;
            UrlToClipboardCheckBox.IsChecked = options.IsUrlToClipboardCheckBox;
            QuickUploadCheckBox.IsChecked = options.IsQuickUploadCheckBoxChecked;
            //RegistryCheckBox.IsChecked = Contextmenue.IsRegistryKeySet();
            LanguageSelection.SelectedItem = options.SelectedLanguage.Equals("de") ? GermanItemFlag : EnglishItemFlag;
        }

        /// <summary>
        /// When the main window is loaded
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        void MainWindow_Loaded(object sender, RoutedEventArgs e)
        {
            CheckIfUpdateIsAvailable();
        }

        /// <summary>
        /// To check if an update is avaialble
        /// </summary>
        private void CheckIfUpdateIsAvailable()
        {
            UpdateManager updtManager = new UpdateManager();

            //Register the event which will be fired when the checking of upgrade is over
            updtManager.OnUpdateCheck += new UpdateManager.UpdateCheckingHanlder(updtManager_OnUpdateCheck);
            updtManager.UpdateChecker();
        }

        /// <summary>
        /// Event handler when upgrade checking is over
        /// </summary>
        /// <param name="bVal">Indicates whether there is an update or not</param>
        void updtManager_OnUpdateCheck(bool bVal)
        {
            if (bVal)
            {
                //Set the icon if update is available
                Dispatcher.Invoke((Action)(delegate
                                               {
                                                   Uri imageURI = new Uri("pack://application:,,,/UploadClient;component/media/update_icon_25.png");
                                                   BitmapImage bmpImg = new BitmapImage(imageURI);
                                                   imgUpdate.Source = bmpImg;

                                               }));


            }
            else
            {
                Dispatcher.Invoke((Action)(delegate
                                               {
                  
                                                   imgUpdate.Source = null;

                                               }));
                
            }

        }

        /// <summary>
        /// Initialize TrayIcon.
        /// </summary>
        /// <param name="programName">Name of the program.</param>
        private void InitTrayIcon(string programName)
        {
            trayIcon.BalloonTipText = LocalizationManager.ResourceManager.GetString("TRA_0001");
            trayIcon.BalloonTipTitle = programName;
            trayIcon.BalloonTipIcon = ToolTipIcon.Info;
            trayIcon.Text = programName;

            Stream iconStream = Application.GetResourceStream(new Uri("pack://application:,,,/UploadClient;component/Media/box_upload_48.ico")).Stream;
            trayIcon.Icon = new Icon(iconStream);

            trayMenuExit.Text = LocalizationManager.ResourceManager.GetString("TRA_0002");
            trayMenuExit.Click += new EventHandler(TrayMenuExit_Click);
            trayMenu.Items.Add(trayMenuExit);
            trayIcon.ContextMenuStrip = trayMenu;
            trayIcon.Click += new EventHandler(TrayIcon_Click);
        }

        #endregion

        #region OnClick

        /// <summary>
        /// Disable TrayIcon and Enables the MainWindow.
        /// </summary>
        void TrayIcon_Click(object sender, EventArgs e)
        {
            if (((MouseEventArgs)e).Button == MouseButtons.Left)
            {
                this.Show();
                this.WindowState = WindowState.Normal;
                trayIcon.Visible = false;
            }
        }

        /// <summary>
        ///  When the update button is clicked
        /// </summary>        
        private void imgUpdate_MouseDown(object sender, MouseButtonEventArgs e)
        {
            MessageBoxResult result = MessageBox.Show("An Upgrade is available.Do you want to update.It will cause the application to restart.", "FtpUploadClient Upgrade", MessageBoxButton.YesNo, MessageBoxImage.Question);

            if (result == MessageBoxResult.Yes)
            {
                if (File.Exists("Updates.xml"))
                {
                    PerformUpdate();
                }
                else
                {
                    UpdateManager upManager = new UpdateManager();
                    upManager.ChkAndUpgrade();
                }
            }

        }


        /// <summary>
        /// Open FileDialoge.
        /// </summary>
        private void BrowseButton_Click(object sender, RoutedEventArgs e)
        {
            if (true)//!ftpUpload.IsBusy)
            {
                OpenFileDialog openDialoge = new OpenFileDialog();
                openDialoge.Multiselect = true;

                if (openDialoge.ShowDialog() == true)
                {
                    UploadProgressBar.Value = 0;

                    foreach (string path in openDialoge.FileNames)
                        filepath.Add(new UploadItem { Filepath = path });

                    UpdateGuiFilecount();
                }
            }
            else
            {
                ExceptionHandling.ThrowMessage(new CustomKeyException("ERR_0008",
                                                                      LocalizationManager.ResourceManager.GetString("ERR_0009"),
                                                                      SystemIcons.Exclamation.ToBitmap()));
            }
        }

        /// <summary>
        /// Starts the download async.
        /// </summary>
        private void StartDownloadButton_Click(object sender, RoutedEventArgs e)
        {
            if (true)//!ftpUpload.IsBusy)
            {
                CancelDownloadButton.IsEnabled = true;
                if (options.IsQuickUploadCheckBoxChecked
                    && settings.FavouriteConnection != null
                    && settings.FavouriteConnection.isComplete())
                {
                    ProgressTextBox.Text = LocalizationManager.ResourceManager.GetString("UPL_0006");

                    settings.SelectedConnection = settings.FavouriteConnection;

                    StartDownloadButton.IsEnabled = false;
                    BrowseButton.IsEnabled = false;

                    filepath.ForEach(item => item.ServerSettings = settings.SelectedConnection);
                    //ftpUpload.UploadFiles(filepath.ToArray());
                    CancelDownloadButton.IsEnabled = true;
                }
                else
                {
                    string dllName = LocalizationManager.ResourceManager.GetString("DAT_0004");
                    if (File.Exists(string.Format("{0}\\{1}", Path.GetDirectoryName(System.Windows.Forms.Application.ExecutablePath), dllName)))
                    {
                        settingsWindow = new oldSettingsWindow( settings);
                        settingsWindow.Closing += new CancelEventHandler(SettingsWindow_Closing);
                        this.IsEnabled = false;
                        settingsWindow.Show();
                    }
                    else
                        new CustomKeyException(string.Format(LocalizationManager.ResourceManager.GetString("ERR_0005"), dllName));
                }
            }
            else
            {
                new CustomKeyException(LocalizationManager.ResourceManager.GetString("ERR_0004"));
            }
        }

        /// <summary>
        /// Cancles the download async.
        /// </summary>
        private void CancelDownloadButton_Click(object sender, RoutedEventArgs e)
        {
            filepath.Clear();
            UpdateGuiFilecount();

            //if (ftpUpload.IsBusy)
            //    ftpUpload.CancelUpload();
        }

        /// <summary>
        /// Opens the SettingsWindow.
        /// </summary>
        private void SettingsButton_Click(object sender, RoutedEventArgs e)
        {
            string dllName = LocalizationManager.ResourceManager.GetString("DAT_0004");
            if (File.Exists(string.Format("{0}\\{1}", Path.GetDirectoryName(System.Windows.Forms.Application.ExecutablePath), dllName)))
            {
                settingsWindow = new oldSettingsWindow(settings);
                settingsWindow.OkButton.ToolTip = LocalizationManager.ResourceManager.GetString("UPL_0027");
                settingsWindow.Closing += (s, eArgs) =>
                                              {
                                                  this.IsEnabled = true;
                                                  this.Focus();
                                              };

                this.IsEnabled = false;
                settingsWindow.Show();
            }
            else
                new CustomKeyException(string.Format(LocalizationManager.ResourceManager.GetString("ERR_0005"), dllName));
        }

        #endregion

        #region Window/Tray Close(ing)

        /// <summary>
        /// Closes the program.
        /// </summary>
        void TrayMenuExit_Click(object sender, EventArgs e)
        {
            this.Close();
        }

        /// <summary>
        /// Switch to TrayIcon if not visible else close the program.
        /// </summary>
        private void Window_Closing(object sender, CancelEventArgs e)
        {
            if (!trayIcon.Visible)
            {
                //minimize to tray
                e.Cancel = true;
                this.WindowState = WindowState.Minimized;
                trayIcon.BalloonTipText = LocalizationManager.ResourceManager.GetString("TRA_0001");
                trayIcon.Visible = true;
                trayIcon.ShowBalloonTip(500);
                this.Hide();
            }
            else
            {
                // closes the whole application
                trayIcon.Visible = false;

                if (settingsWindow != null)
                    settingsWindow.Close();
                //if (ftpUpload.IsBusy)
                //    ftpUpload.CancelUpload();
            }
        }

        /// <summary>
        /// Starts download async if connection was selected.
        /// </summary>
        void SettingsWindow_Closing(object sender, CancelEventArgs e)
        {
            this.IsEnabled = true;
            this.Focus();

            if (settingsWindow.isTriggertByButton && settings.SelectedConnection != null && settings.SelectedConnection.isComplete())
            {
                ProgressTextBox.Text = LocalizationManager.ResourceManager.GetString("UPL_0006");

                if (true)//!ftpUpload.IsBusy)
                {
                    BrowseButton.IsEnabled = false;
                    StartDownloadButton.IsEnabled = false;

                    filepath.ForEach(item => item.ServerSettings = settings.SelectedConnection);
                    //ftpUpload.UploadFiles(filepath.ToArray());
                    CancelDownloadButton.IsEnabled = true;
                }
                else
                {
                    ProgressTextBox.Text = "";
                    throw new CustomKeyException("ERR_0004");
                }
            }
        }

        #endregion

        #region Optionsmenu 

        #region Expand & shrink option WPF-ExpanderWindow

        private void OptionsExpander_Expanded(object sender, RoutedEventArgs e)
        {
            (FindResource("grow") as Storyboard).Begin(this);
        }

        private void OptionsExpander_Collapsed(object sender, RoutedEventArgs e)
        {
            (FindResource("shrink") as Storyboard).Begin(this);
        }

        #endregion

        private void RegistryCheckBox_Checked(object sender, RoutedEventArgs e)
        {
            //ToDo: maybe Forms.Application.ExecutablePath is faster/saver?
            string programName = Assembly.GetExecutingAssembly().GetName().Name.ToString();
            string path = new FileInfo(Assembly.GetEntryAssembly().Location).DirectoryName.ToString();
            // Contextmenue.AddToConextmenue(LocalizationManager.ResourceManager.GetString("PLG_0003"), string.Format("{0}\\{1}", path, programName));
        }

        private void RegistryCheckBox_Unchecked(object sender, RoutedEventArgs e)
        {
            // Contextmenue.RemoveFromContextmenue();
        }

        private void UrlToClipboardCheckBox_Checked(object sender, RoutedEventArgs e)
        {
            options.IsUrlToClipboardCheckBox = true;
        }

        private void UrlToClipboardCheckBox_Unchecked(object sender, RoutedEventArgs e)
        {
            options.IsUrlToClipboardCheckBox = false;
        }

        private void MonitoringClipboardCheckbox_Checked(object sender, RoutedEventArgs e)
        {
            options.IsMonitoringClipboardCheckboxChecked = true;
            //clipboardMonitoring.EnablePlugin();
        }

        private void MonitoringClipboardCheckbox_Unchecked(object sender, RoutedEventArgs e)
        {
            options.IsMonitoringClipboardCheckboxChecked = false;
            //clipboardMonitoring.DisablePlugin();
        }

        private void QuickUploadCheckBox_Checked(object sender, RoutedEventArgs e)
        {
            options.IsQuickUploadCheckBoxChecked = true;
        }

        private void QuickUploadCheckBox_Unchecked(object sender, RoutedEventArgs e)
        {
            options.IsQuickUploadCheckBoxChecked = false;
        }

        private void LanguageSelection_SelectionChanged(object sender, SelectionChangedEventArgs e)
        {
            if (((sender as ComboBox).SelectedItem as ComboBoxItem).Name.Equals("EnglishItemFlag"))
            {
                options.SelectedLanguage = "en";
                LocalizationManager.UICulture = new CultureInfo("en");
            }
            else if (((sender as ComboBox).SelectedItem as ComboBoxItem).Name.Equals("GermanItemFlag"))
            {
                options.SelectedLanguage = "de";
                LocalizationManager.UICulture = new CultureInfo("de");
            }
        }

        #endregion

        /// <summary>
        /// Called by each programstart. Adds files to the upload queue.
        /// </summary>
        /// <param name="args">The commandline params.</param>
        public void CommandLineArgs(string[] args)
        {
            if (true)//ftpUpload.IsBusy)
            {
                if (!commandLineException)
                {
                    //prevent multiple calls!
                    commandLineException = true;
                    ExceptionHandling.ThrowMessage(new CustomKeyException("ERR_0011",
                                                                          LocalizationManager.ResourceManager.GetString("ERR_0009"),
                                                                          SystemIcons.Information.ToBitmap()));
                }
            }
            else
                if (args.Count() > 0)
                {
                    UploadProgressBar.Value = 0;
                    //ToDo: Check if some work is in progress: bw, openFileDialog, ... before changing something!
                    //ToDo: find out if event interfere with work taht is in progress
                    // use lock() ?

                    // join filepath if its splited at empty spaces
                    string result = string.Join(" ", args);
                    filepath.Add(new UploadItem { Filepath = result });

                    UpdateGuiFilecount();
                }
        }

        /// <summary>
        /// Called from clipboard event. Adds images from clipboard to upload queue.
        /// </summary>
        void ClipboardMonitoring_ClipboardDataChanged()
        {
            if (true)//!ftpUpload.IsBusy)
            {
                if (Clipboard.ContainsImage())
                {
                    // save screenshot local 
                    string picPath = Directory.CreateDirectory(Path.Combine(Path.GetDirectoryName(System.Windows.Forms.Application.ExecutablePath), LocalizationManager.ResourceManager.GetString("DAT_0001"))).FullName.ToString();
                    string pic = string.Format("{0}\\{1}.png", picPath, DateTime.Now.ToString("MMddyyHmmss"));
                    ImageHelpers.SaveClipboardImageToFile(pic);

                    filepath.Add(new UploadItem { Filepath = pic });
                    UpdateGuiFilecount();
                }
            }
            else
                ExceptionHandling.ThrowMessage(new CustomKeyException("ERR_0010",
                                                                      LocalizationManager.ResourceManager.GetString("ERR_0009"),
                                                                      SystemIcons.Information.ToBitmap()));
        }

        private void PerformUpdate()
        {
            UpdateManager upManager = new UpdateManager();
            upManager.StartUpdater();

        }
        /// <summary>
        /// Updates the GUI/Tray if files are selected.
        /// </summary>
        void UpdateGuiFilecount()
        {
            if (filepath.Count > 0)
            {
                if (filepath.Count == 1)
                    ProgressTextBox.Text = string.Format(LocalizationManager.ResourceManager.GetString("UPL_0002"), filepath.First());
                else ProgressTextBox.Text = string.Format(LocalizationManager.ResourceManager.GetString("UPL_0003"), filepath.Count.ToString());

                if (this.Visibility.Equals(Visibility.Hidden))
                {
                    trayIcon.BalloonTipText = string.Format(LocalizationManager.ResourceManager.GetString("TRA_0003"), filepath.Count());
                    trayIcon.ShowBalloonTip(500);
                }
                else
                {
                    //Window to front
                    this.Topmost = true;
                    this.Topmost = false;
                }

                StartDownloadButton.IsEnabled = true;
                CancelDownloadButton.IsEnabled = true;
            }
            else
            {
                ProgressTextBox.Text = "";
                trayIcon.BalloonTipText = "";
                StartDownloadButton.IsEnabled = false;
                CancelDownloadButton.IsEnabled = false;
                BrowseButton.IsEnabled = true;
            }
        }

        #region IHost interface implementation

        public void AddToUploadlist(string path)
        {
            if (true)//!ftpUpload.IsBusy)
            {
                filepath.Add(new UploadItem { Filepath = path });
                UpdateGuiFilecount();
            }
            else
                ExceptionHandling.ThrowMessage(new CustomKeyException("ERR_0010",
                                                                      LocalizationManager.ResourceManager.GetString("ERR_0009"),
                                                                      SystemIcons.Information.ToBitmap()));
        }

        public Window GetWindowHandle()
        {
            return this;
        }

        public string GetTempFileDir()
        {
            return Directory.CreateDirectory(Path.Combine(Path.GetDirectoryName(System.Windows.Forms.Application.ExecutablePath), 
                                                          LocalizationManager.ResourceManager.GetString("DAT_0001"))
                ).FullName.ToString();
        }

        public string GetProgramName()
        {
            return Assembly.GetExecutingAssembly().GetName().Name.ToString();
        }

        public string GetExecutingAssemblyLocation()
        {
            return Assembly.GetExecutingAssembly().Location;
        }

        public string GetExecutingAssemblyDirectoryName()
        {
            return new FileInfo(Assembly.GetEntryAssembly().Location).DirectoryName.ToString();
        }

        public string GetProgramVersion()
        {
            return Assembly.GetExecutingAssembly().GetName().Version.ToString();
        }

        public void ThrowException(Exception ex)
        {
            ExceptionHandling.ThrowMessage(ex);
        }

        public void SetLocalizationRessourceDictionarys(Dictionary<string, Dictionary<string, string>> dictionarys)
        {
            //ToDo:....
        }

        public string GetLocalizationRessourceString(string key)
        {
            //ToDo:...
            return key;
        }

        #endregion

        #region Backgroundworker

        /// <summary>
        /// Displays the progress of the async upload.
        /// </summary>
        private void Upload_ProgressChanged(UploadProgressEventArgs e)
        {
            if (this.WindowState.Equals(WindowState.Minimized))
                trayIcon.Text = e.Message;
            else
            {
                UploadProgressBar.Value = Math.Min(UploadProgressBar.Maximum, e.ProgressPercentage);
                ProgressTextBox.Text = e.Message.ToString();	// the message will be something like: 45 Kb / 102.12 Mb
            }
        }

        /// <summary>
        /// Displays the result of the async upload.
        /// If defined it copys the url of the last file into the clipboard.
        /// </summary>
        private void Upload_RunWorkerCompleted(UploadEventArgs e)
        {
            if (e.Error != null)
            {
                UploadProgressBar.Value = 0;
                ProgressTextBox.Text = "";
                ExceptionHandling.ThrowMessage(e.Error);

                //ToDo: what to do with the used settings? delete from list/serializastion? -> filter errortype!
                MessageBoxResult result = MessageBox.Show(LocalizationManager.ResourceManager.GetString("UPL_0017"),
                                                          LocalizationManager.ResourceManager.GetString("UPL_0018"),
                                                          MessageBoxButton.YesNo);

                if (result.Equals(MessageBoxResult.Yes))
                {
                    settings.Remove(settings.SelectedConnection);
                    settings.SelectedConnection = null;
                }
            }
            else if (e.Cancelled)
            {
                UploadProgressBar.Value = 0;
                ProgressTextBox.Text = LocalizationManager.ResourceManager.GetString("UPL_0009");
            }
            else //complete without cancle or errors
            {
                ProgressTextBox.Text = LocalizationManager.ResourceManager.GetString("UPL_0010");

                if (options.IsUrlToClipboardCheckBox)
                {
                    StringBuilder url = new StringBuilder();

                    if (settings.SelectedConnection.Host.ToLower().StartsWith("ftp://"))
                        url.Append(settings.SelectedConnection.Host.Substring(4));
                    else url.Append(settings.SelectedConnection.Host);

                    url.Append("/");
                    url.Append(filepath.FirstOrDefault().Filename);

                    Clipboard.SetData(DataFormats.Text, url);
                }
            }

            filepath.Clear();
            commandLineException = false;
            BrowseButton.IsEnabled = true;
            CancelDownloadButton.IsEnabled = false;
        }

        #endregion
    }
}
